/*
 *    Geotoolkit - An Open Source Java GIS Toolkit
 *    http://www.geotoolkit.org
 *
 *    (C) 2008 - 2009, Geomatys
 *
 *    This library is free software; you can redistribute it and/or
 *    modify it under the terms of the GNU Lesser General Public
 *    License as published by the Free Software Foundation; either
 *    version 2.1 of the License, or (at your option) any later version.
 *
 *    This library is distributed in the hope that it will be useful,
 *    but WITHOUT ANY WARRANTY; without even the implied warranty of
 *    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 *    Lesser General Public License for more details.
 */
package org.geotoolkit.util.collection;

import java.util.ArrayList;
import java.util.Collection;
import java.util.Collections;
import java.util.EventObject;

import org.apache.sis.measure.NumberRange;


/**
 * Event generated by "living" lists.
 *
 * @author Johann Sorel (Geomatys)
 * @module
 */
public class CollectionChangeEvent<T> extends EventObject{

    private static final long serialVersionUID = 4003873381282325130L;

    public static final int ITEM_ADDED = 1;
    public static final int ITEM_REMOVED = 2;
    public static final int ITEM_CHANGED = 3;

    private final NumberRange range;
    private final int type;
    private final Collection<T> items;
    private final EventObject subEvent;

    public CollectionChangeEvent(final Object source, final T item, final int type, final NumberRange range, final EventObject event){
        this(source, Collections.singleton(item), type, range, event);
    }

    public CollectionChangeEvent(final Object source, final Collection<? extends T> items, final int type, final NumberRange range, final EventObject event){
        super(source);
        if(type < 1 || type > 3) throw new IllegalArgumentException("invalide type");
        this.range = range;
        this.type = type;
        this.items = Collections.unmodifiableCollection(new ArrayList(items));
        this.subEvent = event;
    }

    /**
     * Returns the range index of the affected items.
     * @return NumberRange or null if the range could not be calculate.
     */
    public NumberRange getRange(){
        return range;
    }

    /**
     * Returns an integer identifying the type of event.
     * Possible values are :
     * - ITEM_ADDED
     * - ITEM_REMOVED
     * - ITEM_CHANGED
     *
     * @return event type : add, remove or change
     */
    public int getType(){
        return type;
    }

    /**
     * Returns the affected items of this event.
     *
     * @return Collection<T> , immutable and never null
     */
    public Collection<T> getItems(){
        return items;
    }

    /**
     * If the type is a change event, then the original EventObject is
     * provided by this method.
     *
     * @return original event or null.
     */
    public EventObject getChangeEvent(){
        return subEvent;
    }

}
